//
// Created by 11510 on 2024/7/8.
//

#ifndef REACTOR_TCPCONNECTION_H
#define REACTOR_TCPCONNECTION_H
#include "SocketIO.h"
#include "Socket.h"
#include "InetAddress.h"
#include <sstream>

class TcpConnection {
private:
    SocketIO _socketIO;

//    调试用，后期可删除
    Socket _sock;
    InetAddress _localAddr;
    InetAddress _peerAddr;

public:
    explicit TcpConnection(int fd) :
            _socketIO(fd), _sock(),
            _localAddr(getLocalAddr()),
            _peerAddr(getPeerAddr()) {}

    ~TcpConnection() = default;

    std::string receive(){
        char buf[(1 << 16) - 1];
        ::memset(buf, 0, sizeof buf);
        _socketIO.readLine(buf, sizeof buf);

        return std::string(buf);
    }

    void send(const std::string& msg){
        _socketIO.writen(msg.c_str(), msg.size());
    }

    std::string toString(){
        std::ostringstream oss;
        oss << _localAddr.ip() << ":"
            << _localAddr.port() << "---->"
            << _peerAddr.ip() << ":"
            << _peerAddr.port();

        return oss.str();
    }

private:
    /* 获取本端与对端的IP地址 */
    InetAddress getLocalAddr() {
        struct sockaddr_in addr;
        socklen_t len = sizeof(struct sockaddr);

        //获取本端地址的函数getsockname
        int ret = getsockname(_sock.getFileDescriptor(), (struct sockaddr *) &addr, &len);
        if (-1 == ret) {
            perror("getsockname");
        }

        return InetAddress(addr);
    }

    InetAddress getPeerAddr(){
        struct sockaddr_in addr;
        socklen_t len = sizeof(struct sockaddr);
        //获取对端地址的函数getpeername
        int ret = getpeername(_sock.getFileDescriptor(), (struct sockaddr *) &addr, &len);
        if (-1 == ret) {
            perror("getpeername");
        }

        return InetAddress(addr);
    }
};


#endif //REACTOR_TCPCONNECTION_H
